package com.dyna.utils;

import cn.hutool.core.util.StrUtil;
import com.dyna.constants.StringPool;
import com.dyna.core.utils.GuavaCacheUtil;
import com.dyna.domain.dto.KeyValue;
import com.dyna.foundation.domain.entity.SysDictType;
import com.dyna.foundation.feign.FoundationDictApi;
import com.google.common.cache.CacheLoader;
import com.google.common.cache.LoadingCache;
import com.google.common.cache.RemovalCause;
import lombok.SneakyThrows;
import lombok.extern.slf4j.Slf4j;

import javax.validation.constraints.NotNull;
import java.time.Duration;
import java.util.ArrayList;
import java.util.List;

/**
 * @author zhoucaiwang
 */

@Slf4j
public class DictLocalCacheUtil {

    private static FoundationDictApi dictDataApi;

    private static final SysDictType DEFAULT_DICT_DATA = new SysDictType();

    private static final List<SysDictType> DEFAULT_DICT_DATA_LIST = new ArrayList<>();

    /**
     * guava 缓存
     */
    private static final LoadingCache<KeyValue<String, String>, SysDictType> GET_DICT_DATA_CACHE = GuavaCacheUtil.buildAsyncReloadingCache(
            Duration.ofSeconds(4),
            notification -> {
                // 监听到的元素
                log.info("开始监听1");
                KeyValue<String, String> key = notification.getKey();
                // 移除原因
                RemovalCause cause = notification.getCause();
                log.info("元素【{}】, 因为{}被移除了",key,cause);
            },
            new CacheLoader<KeyValue<String, String>, SysDictType>() {
                @NotNull
                @Override
                public SysDictType load(@NotNull KeyValue<String, String> key) {
                    log.info("guava加载具体字典数据···");
                    // TODO guava缓存
//                    return ObjectUtil.defaultIfNull(dictDataApi.queryOne(key.getKey(), key.getValue()).getData(), DEFAULT_DICT_DATA);
                    return null;
                }
            }
    );

    private static final LoadingCache<KeyValue<String, String>, List<SysDictType>> GET_DICT_TYPE_DATA_CACHE = GuavaCacheUtil.buildAsyncReloadingCache(
            Duration.ofSeconds(4),
            notification -> {
                // 监听到的元素
                log.info("开始监听2");
                KeyValue<String, String> key = notification.getKey();
                // 移除原因
                RemovalCause cause = notification.getCause();
                log.info("元素【{}】, 因为{}被移除了",key,cause);
            },
            new CacheLoader<KeyValue<String, String>, List<SysDictType>>() {
                @NotNull
                @Override
                public List<SysDictType> load(@NotNull KeyValue<String, String> key) {
                    log.info("guava加载指定类型字典数据···");
                    // TODO guava缓存
//                    return CollUtil.defaultIfEmpty(dictDataApi.queryByType(key.getKey()).getData(), DEFAULT_DICT_DATA_LIST);
                    return null;
                }
            }
    );

    /**
     * 初始化 FoundationDictApi
     * @param dictDataApi 远程调用字典接口
     */
    public static void init(FoundationDictApi dictDataApi) {
        DictLocalCacheUtil.dictDataApi = dictDataApi;
        log.info("[init][初始化 DictLocalCacheUtil 成功]");
    }

    @SneakyThrows
    public static String getDictDataLabel(String dictType, String dictValue) {
        if (StrUtil.isBlank(dictValue)) {
            dictValue = StringPool.EMPTY;
        }
        return GET_DICT_DATA_CACHE.get(new KeyValue<>(dictType, dictValue)).getDictType();
    }

    @SneakyThrows
    public static List<SysDictType> getDictDataByType(String dictType) {
        return GET_DICT_TYPE_DATA_CACHE.get(new KeyValue<>(dictType,StringPool.EMPTY));
    }

}
